package com.kaaction.modules.eb.api;

import static org.slf4j.MDC.get;

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.UnsupportedEncodingException;
import java.net.MalformedURLException;
import java.net.URL;
import java.net.URLConnection;
import java.util.ArrayList;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;
import java.util.UUID;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.apache.commons.codec.digest.DigestUtils;
import org.apache.commons.httpclient.NameValuePair;
import org.dom4j.Document;
import org.dom4j.DocumentException;
import org.dom4j.DocumentHelper;
import org.dom4j.Element;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;

import com.google.gson.Gson;
import com.kaaction.common.utils.StringUtils;
import com.kaaction.common.web.BaseController;
import com.kaaction.modules.eb.entity.Customer;
import com.kaaction.modules.eb.entity.Order;
import com.kaaction.modules.eb.entity.OrderProduct;
import com.kaaction.modules.eb.entity.Product;
import com.kaaction.modules.eb.service.CustomerService;
import com.kaaction.modules.eb.service.OrderProductService;
import com.kaaction.modules.eb.service.OrderService;
import com.kaaction.modules.market.entity.Event;
import com.kaaction.modules.market.service.EventService;
import com.kaaction.modules.weixinpay.WeiXinPay;


@Controller
@RequestMapping(value = "/api/v1/eb/pay")
public class WenXinPayController extends BaseController{
	
	/** 商户平台和开发平台约定的API密钥，在商户平台设置 */
    public static final String key="ZC6EGWXA2DXO2OYWWAWKKWQ729GLSYXE";
    /** APP_ID 应用从官方网站申请到的合法appId */
    public static final String WX_APP_ID = "wx079bba8222507669";
    
    @Autowired
	private OrderService orderService;
	
	@Autowired
	private OrderProductService orderProductService;
	
	@Autowired
	private EventService eventService;
	
	@Autowired
	private CustomerService customerService;
	
    
	/**
     * Created by huanghaiming
     * 微信支付跳转支付界面
     * */
    @RequestMapping(value = "/toWeiXinPay")
    public String toWeiXinPay(HttpServletRequest request,HttpServletResponse response,Model mv){
    	
        String code = request.getParameter("code");
        String orderId = request.getParameter("state");
        
        logger.info("当前位置:/api/v1/eb/pay/toWeiXinPay");
        logger.info("code="+code+",订单号="+orderId);
        
        double realPrice = 0.0;
        if(!StringUtils.isBlank(orderId)){
        	Order order = orderService.get(orderId);
        	OrderProduct orderProduct = orderProductService.getByOrderId(orderId);
            if(order != null && orderProduct != null) {
            	logger.info("找到该记录");
            	realPrice = orderProduct.getProductTotalPrice();
            	String productName = "";
            	Product product = orderProduct.getProduct();
            	if(product != null){
            		productName = product.getName();
            	}
            	logger.info("商品名称为"+productName);
            	logger.info("应付金额为"+realPrice);
            	logger.info("从微信获取openid");
            	
            	
            	String url = "https://api.weixin.qq.com/sns/oauth2/access_token?appid=wx079bba8222507669&secret=fa10d617075d0a950bec57977d3117ce&code="+code+"&grant_type=authorization_code";
                String json = loadJson(url);
                Gson gs = new  Gson();

                Map<String,String> map = gs.fromJson(json, Map.class);
                String access_token =map.get("access_token");
                String openid =map.get("openid");
                String unionid =map.get("unionid");
                logger.info("openid="+openid+",unionid="+unionid+",access_token="+access_token);
                request.getSession().setAttribute("openid", openid);
                logger.info("save buyer's openid in order successfully...");
                
                
                Customer customer = customerService.getByOpenId(openid);
                if(customer!=null && !StringUtils.isBlank(customer.getId())){
                	logger.info("customer exists now ,id: "+ customer.getId());
                } else {
                	customer = new Customer();
                	customer.setThirdpartyChannel("wechat");
                    customer.setThirdpartyId(openid);
                    customerService.save(customer);
                    logger.info("customer not exists ,new id: "+ customer.getId());
                }
                
                order.setCustomer(customer);
                orderService.save(order);
                logger.info("save buyer's openid in order");
                request.getSession().setAttribute("customerid", customer.getId());
                
                String ip ="118.178.124.242";
                WeiXinPay weiXinPay = new WeiXinPay();
                String result=get("xml");
                try {
                    result = weiXinPay.submitOrder(request,productName,realPrice,0,ip,openid,orderId);
                } catch (UnsupportedEncodingException e) {
                    e.printStackTrace();
                }
                Document doc = null;
                try {
                    doc = DocumentHelper.parseText(result);
                } catch (DocumentException e) {
                    e.printStackTrace();
                }
                Element root = doc.getRootElement();
                Element  prepay_id = root.element("prepay_id");
                String prepay_id_text = prepay_id.getText();
                //System.out.print(prepay_id_text);
                String nonce_str = UUID.randomUUID().toString().replace("-", "");
                String packages = "prepay_id="+prepay_id_text;
                String signType="MD5";
                List<NameValuePair> nvps = new ArrayList<NameValuePair>();
                nvps.add(new NameValuePair("appId", WX_APP_ID));
                nvps.add(new NameValuePair("nonceStr",  nonce_str));
                nvps.add(new NameValuePair("package", packages));
                nvps.add(new NameValuePair("signType", signType));
                nvps.add(new NameValuePair("timeStamp",String.valueOf(System.currentTimeMillis()).toString().substring(0,10)));
                StringBuffer sb = new StringBuffer();

                for (NameValuePair nvp : nvps) {
                    sb.append(nvp.getName() + "=" + nvp.getValue() + "&");
                }

                String signA = sb.toString(); // 根据签名格式组装数据，详见微信支付api
                String stringSignTemp = signA + "key=" + key; // 根据签名格式组装数据，详见微信支付api
                logger.info("stringSignTemp=" + stringSignTemp);
                String sign = DigestUtils.md5Hex(
                        WeiXinPay.getContentBytes(stringSignTemp, "UTF-8")).toUpperCase();
                //System.out.print("SIGN="+sign);
                mv.addAttribute("prepay_id",prepay_id_text);
                mv.addAttribute("timeStamp",String.valueOf(System.currentTimeMillis()).toString().substring(0,10));
                mv.addAttribute("nonce_str",nonce_str);
                mv.addAttribute("sign",sign);
                mv.addAttribute("orderId",orderId);
            }
        }
        return "modules/eb/toWeixinPay";
    }
    
    public static String loadJson (String url) {
        StringBuilder json = new StringBuilder();
        try {
            URL urlObject = new URL(url);
            URLConnection uc = urlObject.openConnection();
            BufferedReader in = new BufferedReader(new InputStreamReader(uc.getInputStream()));
            String inputLine = null;
            while ( (inputLine = in.readLine()) != null) {
                json.append(inputLine);
            }
            in.close();
        } catch (MalformedURLException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        }
        return json.toString();
    }
    
    
    @RequestMapping(value = "/kdNotify", method = RequestMethod.POST)
	public void kdNotify(HttpServletRequest request,
			HttpServletResponse response) throws IOException, DocumentException {

		BufferedReader reader = request.getReader();
		String line = "";
		StringBuffer inputString = new StringBuffer();

		while ((line = reader.readLine()) != null) {
			inputString.append(line);
		}
		request.getReader().close();
		System.out.println("----接收到的报文---" + inputString.toString());

		Document doc = DocumentHelper.parseText(inputString.toString());
		Element root = doc.getRootElement();
		Map<String, Object> map = (Map<String, Object>) xml2map(root);
		String out_trade_no = String.valueOf(map.get("out_trade_no"));
		String return_code = String.valueOf(map.get("return_code"));
		String result_code = String.valueOf(map.get("result_code"));

		if ("SUCCESS".equals(return_code) && "SUCCESS".equals(result_code)) {
			//photographerService.updateOrder(out_trade_no);
			System.out.println("=============支付成功，更新订单状态================");
			Order order = orderService.get(out_trade_no);
			order.setStatus("020");
			orderService.save(order);
			
		}
		response.getWriter().write("SUCCESS");
		;
	}

    private Map xml2map(Element e) {
		Map map = new LinkedHashMap();
		List list = e.elements();
		if (list.size() > 0) {
			for (int i = 0; i < list.size(); i++) {
				Element iter = (Element) list.get(i);
				List mapList = new ArrayList();

				if (iter.elements().size() > 0) {
					Map m = xml2map(iter);
					if (map.get(iter.getName()) != null) {
						Object obj = map.get(iter.getName());
						if (!(obj instanceof List)) {
							mapList = new ArrayList();
							mapList.add(obj);
							mapList.add(m);
						}
						if (obj instanceof List) {
							mapList = (List) obj;
							mapList.add(m);
						}
						map.put(iter.getName(), mapList);
					} else
						map.put(iter.getName(), m);
				} else {
					if (map.get(iter.getName()) != null) {
						Object obj = map.get(iter.getName());
						if (!(obj instanceof List)) {
							mapList = new ArrayList();
							mapList.add(obj);
							mapList.add(iter.getText());
						}
						if (obj instanceof List) {
							mapList = (List) obj;
							mapList.add(iter.getText());
						}
						map.put(iter.getName(), mapList);
					} else
						map.put(iter.getName(), iter.getText());
				}
			}
		} else
			map.put(e.getName(), e.getText());
		return map;
	}

}
